/**
 *
 */
package com.fita.webpay.entity.prepare;

import java.util.HashMap;
import java.util.Map;

import org.apache.commons.lang3.StringUtils;
import com.fita.webpay.entity.context.HandpayContext;
import com.fita.webpay.entity.context.WechatpayContext;
import com.fasterxml.jackson.annotation.JsonIgnore;

/**
 * @author downpour
 *
 */
public class PrepareResponse {

    private String code;

    private String message;

    private Map<String, Object> data;

    /**
     * The default constructor
     */
    public PrepareResponse() {
        this.code = "1";
        this.data = new HashMap<String, Object>();
    }

    /**
     *
     * @param code
     */
    public PrepareResponse(String code) {
        this.code = code;
        this.data = new HashMap<String, Object>();
    }

    /**
     *
     * @param wechatpayAppContext
     * @return
     */
    public PrepareResponse data(WechatpayContext wechatpayAppContext) {
        return this.data("appId", wechatpayAppContext.getAppId())
                   .data("package", wechatpayAppContext.getPackageValue())
                   .data("nonceStr", wechatpayAppContext.getNonceStr())
                   .data("timestamp", wechatpayAppContext.getTimestamp())
                   .data("paySign", wechatpayAppContext.getPaySign());
    }
    
    public PrepareResponse data(HandpayContext handpayContext) {
        return this.data("insCode", handpayContext.getInsCode())
                   .data("insMerchantCode", handpayContext.getInsMerchantCode())
                   .data("hpMerCode", handpayContext.getHpMerCode())
                   .data("orderNo", handpayContext.getOrderNo())
                   .data("orderTime", handpayContext.getOrderTime())
                   .data("currencyCode", handpayContext.getCurrencyCode())
                   .data("orderAmount", handpayContext.getOrderAmount())
                   .data("name", handpayContext.getName())
                   .data("idNumber", handpayContext.getIdNumber())
                   .data("accNo", handpayContext.getAccNo())
                   .data("telNo", handpayContext.getTelNo())
                   .data("productType", handpayContext.getProductType())
                   .data("paymentType", handpayContext.getPaymentType())
                   .data("nonceStr", handpayContext.getNonceStr())
                   .data("backUrl", handpayContext.getBackUrl())
                   .data("signature", handpayContext.getSignature());
    }

    /**
     * Initialize with code and message
     *
     * @param code
     * @param message
     * @return
     */
    public PrepareResponse initialize(String code, String message) {
        this.code = code;
        this.message = message;
        return this;
    }

    /**
     * Mark with success flag and status code
     *
     * @return
     */
    public PrepareResponse success() {
        this.code = "0";
        return this;
    }

    /**
     * Mark with fail flag and status code
     *
     * @return
     */
    public PrepareResponse fail() {
        this.code = "1";
        return this;
    }

    /**
     *
     * @param code
     * @return
     */
    public PrepareResponse fail(String code) {
        this.code = code;
        return this;
    }

    /**
     * Add message for result
     *
     * @param message
     * @return
     */
    public PrepareResponse message(String message) {
        this.message = message;
        return this;
    }

    /**
     * Add data for result
     *
     * @param key
     * @param value
     * @return
     */
    public PrepareResponse data(String key, Object value) {
        this.data.put(key, value);
        return this;
    }

    /**
     * Add data for result
     *
     * @param data
     * @return
     */
    public PrepareResponse data(Map<String, ? extends Object> data) {
        this.data.putAll(data);
        return this;
    }

    /**
     * Determine whether the status is valid
     *
     * @return
     */
    @JsonIgnore
    public boolean isValid() {
        return StringUtils.equals(this.code, "0");
    }

    /**
     * Get data according to key
     *
     * @param key
     * @return
     */
    public Object get(String key) {
        return this.data.get(key);
    }

    /**
     * @return the code
     */
    public String getCode() {
        return code;
    }

    /**
     * @return the message
     */
    public String getMessage() {
        return message;
    }

    /**
     * @return the data
     */
    public Map<String, Object> getData() {
        return data;
    }

    /**
     * @param code the code to set
     */
    public void setCode(String code) {
        this.code = code;
    }

    /**
     * @param message the message to set
     */
    public void setMessage(String message) {
        this.message = message;
    }

    /**
     * @param data the data to set
     */
    public void setData(Map<String, Object> data) {
        this.data = data;
    }

}
